package com.beta.inventory.mockito;

import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.is;
import static org.hamcrest.collection.IsIn.isIn;
import static org.mockito.BDDMockito.willDoNothing;
import static org.mockito.Matchers.anyString;
import static org.mockito.Mockito.verify;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.runners.MockitoJUnitRunner;

import com.beta.inventory.PullListener;
import com.beta.inventory.SimpleSpot;

@RunWith(MockitoJUnitRunner.class)
public class SimpleSpotBehavior {

	// object under test
	@InjectMocks private SimpleSpot spot = new SimpleSpot();
	
	// dependencies
	@Mock private PullListener listener;
	
	@Test public void shouldStoreReceivedSignals() {
		
		// Given a signal Time to replenish
		String signal = "Time to replenish";
		
		// When the signal is received two times
		spot.receiveSignal(signal);
		spot.receiveSignal(signal);
		
		// Then it should be stored twice for future processing
		assertThat(signal , isIn(spot.signals()));
		assertThat(spot.count(signal) , is(2));
	}
	
	@Test public void shouldNotifyObserverWhenProcessSignal() {
		String signal = "Time to replenish";
		assertThat(spot.count(signal) , is(0));
		
		
		spot.receiveSignal(signal);
		spot.receiveSignal(signal);
		
		// define observer interaction
		willDoNothing().given(listener).replenish(anyString());
		
		// assertion before pull
		assertThat(spot.count(signal) , is(2));
		
		// When
		spot.processSignal(signal);
		
		// verify observer interaction
		verify(listener).replenish(anyString());
		
		// assertion before pull
		assertThat(spot.count(signal) , is(1));
	}
}
